/*
 * Copyright 2010 Mario Zechner (contact@badlogicgames.com), Nathan Sweet (admin@esotericsoftware.com)
 * 
 * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the
 * License. You may obtain a copy of the License at
 * 
 * http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS"
 * BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language
 * governing permissions and limitations under the License.
 */

package com.badlogic.gdxinvaders.screens;

import com.badlogic.gdx.Application;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.Files.FileType;
import com.badlogic.gdx.Input;
import com.badlogic.gdx.Input.Keys;
import com.badlogic.gdx.audio.Sound;
import com.badlogic.gdx.graphics.GL10;
import com.badlogic.gdxinvaders.Constants;
import com.badlogic.gdxinvaders.Renderer;
import com.badlogic.gdxinvaders.simulation.Simulation;
import com.badlogic.gdxinvaders.simulation.SimulationListener;
import com.deadpixel.constant.Constant;
import com.deadpixel.constant.ConstantEditor;
import com.deadpixel.constant.ConstantEditorListener;
import com.deadpixel.constant.ConstantManager;

public class GameLoop implements Screen, SimulationListener {
	/** the simulation **/
	private final Simulation simulation;
	/** the renderer **/
	final Renderer renderer;
	/** explosion sound **/
	private final Sound explosion;
	/** shot sound **/
	private final Sound shot;
	
	/** constant manager **/
	private ConstantManager constantManager;
	
	/** constant editor **/
	private ConstantEditor	constantEditor;
	
	boolean         paused;

	public GameLoop (Application app) {
		
		paused = false;
		constantManager = new ConstantManager("data/constants/constants", "Invaders/constants");
		constantManager.log(true);
		Constants.CreateConstants(constantManager);
		
		constantEditor	= new ConstantEditor(constantManager, "data/constants/ConstantEditorSkin", Gdx.graphics.getWidth(), Gdx.graphics.getHeight());
		Gdx.input.setInputProcessor(constantEditor.getInputProcessor());
		
		constantEditor.setListener(new ConstantEditorListener() {
			
			@Override
			public void onOpening() {
				paused = true;
			}
			
			@Override
			public void onClosing() {
				paused = false;
			}

			@Override
			public void onConstantChanged(Constant constant) {
				
				if(constant == Constants.CAMERA_FOV)
				{
					renderer.setFOV(Constants.CAMERA_FOV.get());
				}
			}
		});
		
		
		simulation = new Simulation();
		simulation.listener = this;
		renderer = new Renderer(app);
		explosion = app.getAudio().newSound(app.getFiles().getFileHandle("data/explosion.ogg", FileType.Internal));
		shot = app.getAudio().newSound(app.getFiles().getFileHandle("data/shot.ogg", FileType.Internal));
		
		
		resize(Gdx.graphics.getWidth(), Gdx.graphics.getHeight());
	}

	@Override
	public void dispose () {
		renderer.dispose();
		shot.dispose();
		explosion.dispose();
		
		if(constantEditor != null)
			constantEditor.dispose();
	}

	@Override
	public boolean isDone () {
		return !paused && simulation.ship.lives == 0;
	}

	@Override
	public void render (Application app) {
		app.getGraphics().getGL10().glClear(GL10.GL_COLOR_BUFFER_BIT | GL10.GL_DEPTH_BUFFER_BIT);
	
		renderer.render(app, simulation);
		
		if(constantEditor != null)
			constantEditor.render(app.getGraphics().getDeltaTime());
	}

	@Override
	public void update (Application app) {
		if(paused)
			return;
		
		simulation.update(app.getGraphics().getDeltaTime());

		Input input = app.getInput();
		if (input.getAccelerometerY() < 0)
			simulation.moveShipLeft(app.getGraphics().getDeltaTime(), Math.abs(input.getAccelerometerY()) / 10);
		else
			simulation.moveShipRight(app.getGraphics().getDeltaTime(), Math.abs(input.getAccelerometerY()) / 10);

		if (input.isKeyPressed(Keys.DPAD_LEFT)) simulation.moveShipLeft(app.getGraphics().getDeltaTime(), 0.5f);
		if (input.isKeyPressed(Keys.DPAD_RIGHT)) simulation.moveShipRight(app.getGraphics().getDeltaTime(), 0.5f);

		if (input.isTouched() || input.isKeyPressed(Keys.SPACE)) simulation.shot();
	}

	@Override
	public void explosion () {
		explosion.play();
	}

	@Override
	public void shot () {
		shot.play();
	}

	@Override
	public void resize(int width, int height) {
		if(constantEditor != null)
			constantEditor.resize(width, height, false);
	}
}
